Skip to content

test(statement): cover dictionary-encoded bind parameter columns - #6

Closed
fornwall wants to merge 2 commits into
mainfrom
test/bind-dictionary-encoded
Closed

test(statement): cover dictionary-encoded bind parameter columns#6
fornwall wants to merge 2 commits into
mainfrom
test/bind-dictionary-encoded

Conversation

@fornwall

Copy link
Copy Markdown
Owner

Split out of #4 (one PR per test). Adds one generic, driver-agnostic test for a gap found while reviewing an ADBC driver (the adbc-spanner Rust driver) against this suite; candidate for upstreaming to adbc-drivers/validation later.

TestStatement.test_parameter_dictionary_encoded (gated on statement_bind)

Binds a dictionary-encoded string column (pa.array([...]).dictionary_encode() — what pandas categoricals produce over the C data interface) and asserts the decoded values (including a null) round-trip via insert + read-back through the existing sample_table fixture / its query_override hook.

  • Origin finding: adbc-spanner REVIEW.md CONV-2 (no Dictionary support on the Arrow-to-database bind path).
  • Spec reference: the Arrow columnar format, "Dictionary-encoded Layout": dictionary encoding is a representation of the same logical values, not a different logical type. No ADBC spec text explicitly requires drivers to accept every Arrow encoding, so this test asserts an ecosystem-consistency expectation stated here explicitly: a driver that binds plain string columns should accept (and may decode) the dictionary-encoded equivalent, since that is what common producers (pandas) emit.

Results on real drivers

  • adbc-spanner (current main): FAIL — verified by an actual emulator run via its foundry harness: INVALID_ARGUMENT: cannot bind parameter "p2": unsupported Arrow type Dictionary(Int32, Utf8).
  • adbc-driver-sqlite 1.11.0 (released PyPI wheel): PASS — verified with a throwaway quirks harness against a temp-file database, demonstrating the contract is satisfiable by an existing reference driver.

Framework checks

uv run pytest tests/ (210 passed, 1 skipped), uv run ty check (clean), pre-commit run --all-files (all hooks pass) — all on this branch independently.

🤖 Generated with Claude Code

https://claude.ai/code/session_01LGf8PVEe2tYkw8Q6Pd95tq

Adds test_parameter_dictionary_encoded, gated on statement_bind: binds
a dictionary-encoded string column (what pandas categoricals produce
over the C data interface) and asserts the decoded values, including a
null, round-trip via insert + read-back through the existing
sample_table fixture and its query_override hook.

Dictionary encoding is an encoding of the same logical values, not a
different logical type (Arrow columnar format, Dictionary-encoded
Layout), so a driver that binds plain string columns should accept the
dictionary-encoded equivalent, decoding it if the database has no
native counterpart.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01LGf8PVEe2tYkw8Q6Pd95tq
Signed-off-by: Fredrik Fornwall <fredrik@fornwall.net>
@fornwall fornwall closed this Jul 14, 2026
fornwall added a commit to fornwall/adbc-spanner that referenced this pull request Jul 14, 2026
…282)

cell_value had no arm for Arrow's Dictionary type, so a dictionary-encoded
column - what pandas categoricals produce over the C data interface - failed
InvalidArguments ("unsupported Arrow type Dictionary(Int32, Utf8)") even
though its value type was supported. Dictionary encoding is an index
representation of the same logical values, not a different logical type
(the Arrow columnar format's "Dictionary-encoded Layout"), so the column now
binds transparently as its value type: the key at each row selects the
dictionary value, which re-enters the same cell mapping - every bindable
value type is accepted encoded, scalars and ARRAY<...> alike, and an
unsupported value type is rejected with the same error as its plain form
(on null cells too, keeping the fail-loudly-on-every-row convention).

Because insert_mutation shares cell_value, mutation-based bulk ingest
decodes the same way, and spanner_column_type sees through the encoding so
the ingest create modes map such a column to its value type's Spanner
column type.

Verified against the emulator via the foundry harness running
fornwall/validation#6's new test_parameter_dictionary_encoded: fails with
the exact CONV-2 error before this change, passes after. Full emulator
cargo test and the pinned upstream foundry suite stay green.


Claude-Session: https://claude.ai/code/session_01FjqdweBVqxdegAHVDh97oV

Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant